/** @format */

import { findPass } from '../utils/findPass'

export class BaseDao {
  private db: any
  constructor(context: any, private dbName: string) {
    this.db = context.cloud.db
    this.dbName = dbName
  }
  /**
   * 查询一条数据
   * @param query
   * @param projection
   */
  async findOne(query: Record<string, any>, projection: Record<string, any> = {}, force = false) {
    const pass = findPass(query, projection, force)
    if (!pass) {
      throw Error('参数存在undefined，不允许继续执行')
    }
    const result = await this.db.collection(this.dbName).find(query, {
      ...projection,
      limit: 1
    })
    return result[0]
  }
  /**
   * 查询多条数据
   * @param query
   * @param projection
   */
  async find(query: Record<string, any>, projection: Record<string, any> = {}, force = false) {
    const pass = findPass(query, projection, force)
    if (!pass) {
      throw Error('参数存在undefined，不允许继续执行')
    }
    return await this.db.collection(this.dbName).find(query, {
      ...projection
    })
  }

  /**
   * 插入单条数据
   * @param document
   */
  async insertOne(document: Record<string, any>) {
    return await this.db.collection(this.dbName).insertOne(document)
  }

  /**
   * 插入多条数据
   * @param documents 插入对象
   */
  async insertMany(documents: Record<string, any>[]) {
    return await this.db.collection(this.dbName).insertMany(documents)
  }

  /**
   * 更新数据
   * @param query
   * @param options
   */
  async update(query: Record<string, any>, options?: Record<string, any>) {
    return await this.db.collection(this.dbName).updateMany(query, options)
  }

  /**
   * 删除多条数据
   * @param filter
   */
  async delete(filter: Record<string, any>) {
    return await this.db.collection(this.dbName).deleteMany(filter)
  }

  /**
   * 获取条目数
   * @param query
   * @param options
   */
  async count(query: Record<string, any>, options?: Record<string, any>) {
    return await this.db.collection(this.dbName).count(query, options)
  }

  /**
   * 聚合查询
   * @param query
   * @param options
   */
  async aggregate(aggregateOperation: Record<string, any> | any[]) {
    return await this.db.collection(this.dbName).aggregate(aggregateOperation)
  }
}
